package com.sky.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.sky.constant.MessageConstant;
import com.sky.constant.StatusConstant;
import com.sky.context.BaseContext;
import com.sky.dto.*;
import com.sky.entity.AddressBook;
import com.sky.entity.OrderDetail;
import com.sky.entity.Orders;
import com.sky.entity.ShoppingCart;
import com.sky.exception.OrderBusinessException;
import com.sky.mapper.AddressMapper;
import com.sky.mapper.OrderDetailMapper;
import com.sky.mapper.OrderMapper;
import com.sky.mapper.ShoppingCartMapper;
import com.sky.result.PageResult;
import com.sky.service.OrderService;
import com.sky.vo.OrderPageQueryVO;
import com.sky.vo.OrderStatisticsVO;
import com.sky.vo.OrderSubmitVO;
import com.sky.vo.OrderVO;
import com.sky.weChatPay.service.impl.WeChatPayServiceImpl;
import com.sky.webSocket.WebSocketServer;
import lombok.extern.slf4j.Slf4j;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

@Service
@Slf4j
public class OrderServiceImpl implements OrderService {

    @Autowired
    private OrderMapper orderMapper;
    @Autowired
    private OrderDetailMapper orderDetailMapper;
    @Autowired
    private AddressMapper addressMapper;
    @Autowired
    private ShoppingCartMapper shoppingCartMapper;
    @Autowired
    private WeChatPayServiceImpl weChatPayService;

    /**
     * 查询历史订单
     * @param ordersPageQueryDTO
     * @return
     */
    @Override
    public PageResult getHistoryOrders(OrdersPageQueryDTO ordersPageQueryDTO) {

        PageHelper.startPage(ordersPageQueryDTO.getPage(), ordersPageQueryDTO.getPageSize());

        List<OrderPageQueryVO> orderPageQueryVOS = orderMapper.getPageQueryOrders(ordersPageQueryDTO);
        
        orderPageQueryVOS.forEach(orderPageQueryVO -> {
            List<OrderDetail> orderDetailList = orderDetailMapper.getOrderDetailByOrderId(orderPageQueryVO.getId());
            StringBuffer dishes = new StringBuffer();
            for (int i = 0; i < orderDetailList.size(); i++) {
                OrderDetail orderDetail = orderDetailList.get(i);
                dishes.append(orderDetail.getName()).append(orderDetail.getNumber()).append("份");
                if(i != orderDetailList.size() - 1){
                    dishes.append(",");
                }
            }
            orderPageQueryVO.setOrderDishes(dishes.toString());
            orderPageQueryVO.setOrderDetailList(orderDetailList);
        });

        //返回PageResult对象
        Page<OrderPageQueryVO> pageQueryVOS = (Page<OrderPageQueryVO>) orderPageQueryVOS;
        return new PageResult(pageQueryVOS.getTotal(), pageQueryVOS.getResult());
    }

    /**
     * 查询订单详情
     * @param id
     * @return
     */
    @Override
    public OrderPageQueryVO getOrderDetailById(Long id) {
        OrderPageQueryVO orderPageQueryVO = new OrderPageQueryVO();
        Orders orders = orderMapper.getOrderById(id);
        List<OrderDetail> orderDetail = orderDetailMapper.getOrderDetailByOrderId(id);
        BeanUtils.copyProperties(orders, orderPageQueryVO);
        orderPageQueryVO.setOrderDetailList(orderDetail);
        return orderPageQueryVO;
    }

    /**
     * 再来一单
     * @param id
     * @return
     */
    @Override
    public void addCommonOrder(Long id) {
        Orders orders = orderMapper.getOrderById(id);

        if(orders == null)throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);

        orders.setNumber(String.valueOf(System.currentTimeMillis()));
        orders.setStatus(Orders.UN_PAID);
        orders.setOrderTime(LocalDateTime.now());
        orders.setEstimatedDeliveryTime(LocalDateTime.now().plusMinutes(60));
        orders.setDeliveryStatus(StatusConstant.ENABLE);
        List<OrderDetail> orderDetailList = orderDetailMapper.getOrderDetailByOrderId(id);

        orderMapper.addOrder(orders);
        id = orders.getId();
        for (OrderDetail orderDetail : orderDetailList) {
            orderDetail.setOrderId(id);
        }
        orderDetailMapper.addOrderDetail(orderDetailList);
    }

    /**
     * 催单
     * @param id
     */
    @Override
    public void reminderOrder(Long id) {
        Orders orders = orderMapper.getOrderById(id);
        //判断业务是否异常
        if(orders == null)throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        weChatPayService.NotifyShopper(2, id, orders.getNumber());
    }

    /**
     * 各个状态的订单数量统计
     * @return
     */
    @Override
    public OrderStatisticsVO getOrderStatistics() {

        int toBeConfirmed = orderMapper.countByStatus(Orders.TO_BE_CONFIRMED);
        int confirmed = orderMapper.countByStatus(Orders.CONFIRMED);
        int deliveryInProgress = orderMapper.countByStatus(Orders.DELIVERY_IN_PROGRESS);
        OrderStatisticsVO orderStatisticsVO = OrderStatisticsVO.builder()
                .toBeConfirmed(toBeConfirmed)
                .confirmed(confirmed)
                .deliveryInProgress(deliveryInProgress)
                .build();
        return orderStatisticsVO;
    }

    /**
     * 接订单
     * @param ordersConfirmDTO
     * @return
     */
    @Override
    public void acceptOrder(OrdersConfirmDTO ordersConfirmDTO) {
        Orders orders = Orders.builder()
                .id(ordersConfirmDTO.getId())
                .status(ordersConfirmDTO.getStatus())
                .build();
        orderMapper.update(orders);
    }

    /**
     * 拒单
     * @param ordersRejectionDTO
     * @return
     */
    @Override
    public void rejectOrders(OrdersRejectionDTO ordersRejectionDTO) {
        Orders orders = Orders.builder()
                .id(ordersRejectionDTO.getId())
                .status(Orders.CANCELLED)
                .amount(BigDecimal.valueOf(0))
                .rejectionReason(ordersRejectionDTO.getRejectionReason())
                .cancelTime(LocalDateTime.now())
                .build();
        orderMapper.update(orders);
    }

    /**
     * 完成订单
     * @param id
     * @return
     */
    @Override
    public void finishOrder(Long id) {
        Orders orders = Orders.builder()
                .id(id)
                .status(Orders.COMPLETED)
                .build();
        orderMapper.update(orders);
    }

    /**
     * 取消订单
     * @param ordersCancelDTO
     * @return
     */
    @Override
    public void cancelOrder(OrdersCancelDTO ordersCancelDTO) {
        Orders orders = orderMapper.getOrderById(ordersCancelDTO.getId());
        if(!Objects.equals(orders.getStatus(), Orders.PENDING_PAYMENT))
        {
            //退款逻辑，但是没有实现
        }
        orders.setCancelTime(LocalDateTime.now());
        orders.setCancelReason(ordersCancelDTO.getCancelReason());
        orders.setStatus(Orders.CANCELLED);
        orders.setPayStatus(Orders.REFUND);
        orderMapper.update(orders);
    }

    /**
     * 提交订单
     * @param ordersSubmitDTO
     * @return
     */
    @Transactional
    @Override
    public OrderSubmitVO submitOrder(OrdersSubmitDTO ordersSubmitDTO) {

        Long userId = BaseContext.getCurrentId();

        //处理各种可能的业务异常（地址簿为空或者购物车为空）
        AddressBook addressBook = addressMapper.getAddressById(ordersSubmitDTO.getAddressBookId());
        if(addressBook == null){
            throw new OrderBusinessException(MessageConstant.ADDRESS_BOOK_IS_NULL);
        }
        ShoppingCart shoppingCartDemo = ShoppingCart.builder().userId(userId).build();
        List<ShoppingCart> shoppingCartList = shoppingCartMapper.getShopingCartByShoppingCart(shoppingCartDemo);
        if(shoppingCartList == null || shoppingCartList.size() == 0){
            throw new OrderBusinessException(MessageConstant.SHOPPING_CART_IS_NULL);
        }

        //把简要订单插入数据库
        Orders orders = new Orders();
        BeanUtils.copyProperties(ordersSubmitDTO, orders);
        BeanUtils.copyProperties(addressBook, orders);
        orders.setUserId(userId);
        orders.setOrderTime(LocalDateTime.now());
        orders.setAddress(addressBook.getDetail());
        orders.setNumber(String.valueOf(System.currentTimeMillis()));
        log.info("judge: {}",  orders.getEstimatedDeliveryTime().isAfter(orders.getOrderTime().plusMinutes(70)));
        log.info(String.valueOf(orders.getEstimatedDeliveryTime()));
        log.info(String.valueOf(orders.getOrderTime()));
        if(orders.getEstimatedDeliveryTime().isAfter(orders.getOrderTime().plusMinutes(70))){
            orders.setDeliveryStatus(StatusConstant.DISABLE);
        }
        orderMapper.addOrder(orders);

        //把订单详情插入表中
        List<OrderDetail> orderDetailList = new ArrayList<OrderDetail>();
        shoppingCartList.forEach(shoppingCart -> {
            OrderDetail orderDetail = new OrderDetail();
            BeanUtils.copyProperties(shoppingCart, orderDetail);
            orderDetail.setOrderId(orders.getId());
            orderDetailList.add(orderDetail);
        });
        orderDetailMapper.addOrderDetail(orderDetailList);

        //清空购物车
        shoppingCartMapper.delete(shoppingCartDemo);

        //返回VO对象
        OrderSubmitVO orderSubmitVO = OrderSubmitVO.builder()
                .id(orders.getId())
                .orderNumber(orders.getNumber())
                .orderAmount(orders.getAmount())
                .orderTime(orders.getOrderTime())
                .build();

//        //测试websocket
//        weChatPayService.NotifyShopper(1, orders.getId(), "订单号：" + orders.getNumber());

        return orderSubmitVO;
    }
}
